package mop.controller;

import java.sql.Timestamp;
import java.util.List;

import mop.domain.resource.*;
import mop.exception.*;

/**
 * The connection between GUI and domain.
 * Only knows built-in Java data types.
 * 
 * @invar 	Has no variables of its own, except for pool,
 * 			which is a reference to a static variable.
 *        
 * @author	MOP Team 7
 */
public class ResourceController 
{

	/**
	 * Creates a ResourceController with no extra settings.
	 * Constructor must be at protected level.
	 * Allows inheritance, but no out of package creation.
	 * 
	 * @post 	pool is set to ResourcePool.getInstance();
	 */
	protected ResourceController()
	{
		this.pool = ResourcePool.getInstance();
	}
	
	
	/***************************************************************************
	 * 							instance
	 ***************************************************************************/
	
	/**
	 * Always use this function to access ResourceController.
	 * 
	 * @return	The static instance of ResourceController.
	 */
	public static ResourceController getInstance()
	{
		if(instance == null) 
		{
	         instance = new ResourceController();
	    }
		return instance;	
	}
	
	/**
	 * instance to self
	 */
	private static ResourceController instance = null;
	
	
	/***************************************************************************
	 * 							resourcePool
	 ***************************************************************************/
	
	/**
	 * Returns a list of all the resources.
	 * 
	 * @return	The list of resource strings from the pool.
	 */
	public List<String> getResourceList()
	{
		return this.pool.getResourceList();
	}
	
	
	/**
	 * Creates a new tool.
	 * 
	 * @param 	description
	 *  		The description of the tool.
	 * 
	 * @post 	A new tool instance is created in the pool.
	 * 
	 * from our lovely pool it throws :
	 * 
	 * @throws 	IllegalDuplicateException
	 * 			if the resource is a duplicate
	 * 			|!isUniqueresource(name)
	 *       
	 * @throws IllegalDescriptionException
	 * 		if the description isn't a non empty string
	 * 		|!isValidDescription(description)
	 */
	public void createTool(String description) 
		throws IllegalDescriptionException, IllegalDuplicationException
	{
		this.pool.addTool(description);
	}
	
	
	/**
	 * Creates a new room.
	 * 
	 * @param 	description
	 *  		The description of the room.
	 * 
	 * @post 	A new room instance is created in the pool
	 * 
	 * from our lovely pool it throws :
	 * 
	 * @throws 	IllegalDuplicateException
	 * 			if the resource is a duplicate
	 * 			|!isUniqueresource(name)
	 *       
	 * @throws 	IllegalDescriptionException
	 * 			if the description isn't a non empty string
	 * 			|!isValidDescription(description)
	 */
	public void createRoom(String description) 
		throws IllegalDescriptionException, IllegalDuplicationException
	{
		this.pool.addRoom(description);
	}
	
	
	/**
	 * Removes a resource from the pool.
	 * 
	 * @param 	description
	 *  		The description of the resource you want to remove from the pool.
	 * 
	 * @pre 	string exists in the resource database, if it doesn't we ignore the remove.
	 * 
	 * @post 	The resource with his description = $description is removed from the pool.
	 * 
	 * @throws 	IllegalTerminationException
	 * 			if the resource is required by a task.
	 */
	public void removeResource(String description) 
		throws IllegalTerminationException
	{
		this.pool.removeResource(description);
	}
	
	/**
	 * Reference to ResourcePool.getInstance(), just to avoid having to write that all the frakking time.
	 */
	private ResourcePool pool;
	
	/***************************************************************************
	 * 						    	 reservation
	 ***************************************************************************/
	
	/**
	 * Adds a reservation for a resource.
	 * 
	 * @param 	resource
	 * 			The resource description.
	 * @param 	start
	 * 			Start time as a Timestamp.
	 * @param 	end
	 * 			End time as a Timestamp.
	 * 
	 * @post	A reservation for the resource is made.
	 * 
	 * @throws	IllegalReservationException
	 * 			If the start time is greater than the end time.
	 * @throws	UnavailableResourceException 
	 * 			If the resource is unavailable at that time.
	 * @throws	IllegalResourceException
	 * 			If the resource does not exist.
	 */
	public void addReservation(String resource, Timestamp start, Timestamp end) 
		throws IllegalResourceException, IllegalReservationException, UnavailableResourceException
	{
		this.pool.addReservation(resource, start, end);
	}
	
	/**
	 * Returns a list of strings representing the reservations for a given resource.
	 * 
	 * @param 	resource
	 * 			The description of a resource.
	 * 
	 * @return	A list of reservation strings.
	 * 
	 * @throws	IllegalResourceException 
	 * 			If the Resource cannot be found.
	 */
	public List<String> getReservations(String resource)
		throws IllegalResourceException
	{
		return this.pool.getReservations(resource);
	}
}